/*
    SUSAN® - Sole of Unix Save ANything

   Copyright (C) 2016-2016 Skyatlas Co. CN

   
*/
/**
 * @file
 * Connection Pool
 *
 * handle/store multiple connections
 */

#ifndef BAREOS_LIB_CONNECTION_POOL_H_
#define BAREOS_LIB_CONNECTION_POOL_H_


class alist;
class BareosSocket;

class Connection {
 public:
  Connection(const char* name,
             int protocol_version,
             BareosSocket* socket,
             bool authenticated = true);
  ~Connection();

  const char* name() { return name_; }
  int protocol_version() { return protocol_version_; }
  BareosSocket* bsock() { return socket_; }
  bool authenticated() { return authenticated_; }
  bool in_use() { return in_use_; }
  time_t ConnectTime() { return connect_time_; }

  bool check(int timeout = 0);
  bool take();

 private:
  void lock() { P(mutex_); }
  void unlock() { V(mutex_); }
  pthread_t tid_;
  BareosSocket* socket_;
  char name_[MAX_NAME_LENGTH];
  int protocol_version_;
  bool authenticated_;
  volatile bool in_use_;
  time_t connect_time_;
  pthread_mutex_t mutex_;
};

class ConnectionPool {
 public:
  ConnectionPool();
  ~ConnectionPool();

  Connection* add_connection(const char* name,
                             int protocol_version,
                             BareosSocket* socket,
                             bool authenticated = true);
  Connection* remove(const char* name, int timeout_in_seconds = 0);
  alist* get_as_alist();
  void cleanup();

 private:
  alist* connections_;
  int WaitForNewConnection(timespec& timeout);
  bool add(Connection* connection);
  bool remove(Connection* connection);
  Connection* get_connection(const char* name);
  Connection* get_connection(const char* name, timespec& timeout);
  pthread_mutex_t add_mutex_;
  pthread_cond_t add_cond_var_;
};
#endif
